/**
 * 事件发布-订阅
 */


interface MyEvent{
  id: Symbol
  event: Function
}

interface MyEventMap{
  [name: string]: Array<MyEvent>
}


export default class EventEmitter{
  emitMap: MyEventMap // 事件订阅表


  constructor(){
    this.emitMap = {}
  }

  
  /**
   * @description: 订阅事件
   * @param {string} name 事件名称
   * @param {Function} event 事件触发时调用函数
   * @return {Symbol}
   */  
  on = (name: string, event?: Function): Symbol => {
    const id = Symbol();

    if(!(name in this.emitMap)) {
      Object.defineProperties(this.emitMap, {
        [name]: {
          value: [],
          enumerable: true,
          writable: true
        }
      })
    }
    
    if(event){
      this.emitMap[name].push({
        id: id,
        event: event
      })
    }
    
    return id
  }


  /**
   * @description: 移除单个事件
   * @param {string} name 事件名称
   * @param {Symbol} id 监听事件on的返回值
   * @return {void}
   */  
  off = (name: string, id: Symbol) => {
    let eventList = this.emitMap[name];
    
    if(eventList){
      var index = eventList.findIndex((item) => item.id === id)
      eventList.splice(index, 1)
    }
  }


  /**
   * @description: 触发事件
   * @param {string} name 事件名称
   * @param {any} params  触发事件时传入的参数集合
   * @return {void}
   */
  emit = (name: string, ...params: any) => {
    let eventList = this.emitMap[name];
    
    if(eventList){
      for(let item of eventList){
        if(typeof item.event == 'function') item.event(...params)
      }
    }
  }


  /**
   * @description: 移除所有事件
   * @return {void}
   */
  disconnect = () => {
    this.emitMap = {}
  }
}